import React, { FC, useState, ChangeEvent } from 'react'
import classNames from 'classnames'
import { Input, message, Button, Space } from 'antd'
import { useDispatch } from 'react-redux'
import { EyeInvisibleOutlined, LockOutlined } from '@ant-design/icons'
import SortableContainer from '../../../../components/DragSortable/SortableContainer'
import SortableItem from '../../../../components/DragSortable/SortableItem'
import {
    changeSelectedId,
    changeComponentTitle,
    invisibleComponent,
    toggleComponentLocked,
    moveComponent,
} from '../../../../store/componentsReducer'
import useGetComponentInfo from '../../../../hooks/useGetComponentInfo'
import styles from './Layers.module.scss'

const Layers: FC = () => {
    const { selectedId, componentsList } = useGetComponentInfo()
    const dispatch = useDispatch()
    const [changingTitleId, setChangingTitleId] = useState('')
    /**
     * 点击选中当前组件
     */
    const handleTitleClick = (fe_id: string) => {
        const currCmp = componentsList.find(c => c.fe_id === fe_id)
        if (currCmp && currCmp.isHidden) {
            message.info('不能选中隐藏的组件')
        }
        // 如果当前组件已经是选中的组件，则return,否则更新store的selectedId
        if (fe_id !== selectedId) {
            // 当前组件未被选中，执行选中更新selectedId
            dispatch(changeSelectedId(fe_id))
            setChangingTitleId('')
            return
        }
        setChangingTitleId(fe_id)
    }
    /**
     * 修改组件标题
     */
    const handleChangeTitle = (event: ChangeEvent<HTMLInputElement>, fe_id: string) => {
        const newTitle = event.target.value.trim()
        if (!newTitle) return
        if (!selectedId) return
        dispatch(changeComponentTitle({ fe_id: selectedId, title: newTitle }))
    }

    /**
     * 切换组件的显示和隐藏
     */
    const handleChangeShowOrHidden = (fe_id: string, isHidden: boolean) => {
        dispatch(invisibleComponent({ fe_id, isHidden }))
    }

    /**
     * 切换组件 锁定/解锁
     */
    const handleLockedStatus = (fe_id: string) => {
        dispatch(toggleComponentLocked({ fe_id }))
    }

    // 拖拽组件SortableContainer 的item需要id，则需要给数据手动添加一个id进去
    const componentsListWithId = componentsList.map(c => {
        return { ...c, id: c.fe_id }
    })

    /**
     * 拖拽结束事件，通过newIndex和oldIndex来重置组件显示顺序
     * @param oldIndex
     * @param newIndex
     */
    const handleDragEnd = (oldIndex: number, newIndex: number) => {
        dispatch(moveComponent({ oldIndex, newIndex }))
    }

    return (
        <SortableContainer items={componentsListWithId} onDragEnd={handleDragEnd}>
            {componentsList.map(c => {
                const { fe_id, title, isLocked, isHidden } = c
                // 拼接title的classnames
                const defaultTitleClass = styles.title
                const selectedTitleClass = styles.selected
                const titleClassName = classNames({
                    [defaultTitleClass]: true,
                    [selectedTitleClass]: selectedId === fe_id,
                })
                return (
                    <SortableItem key={fe_id} id={fe_id}>
                        <div key={fe_id} className={styles.container}>
                            <div className={titleClassName} onClick={() => handleTitleClick(fe_id)}>
                                {changingTitleId === fe_id && (
                                    <Input
                                        value={title}
                                        onChange={e => handleChangeTitle(e, fe_id)}
                                        onPressEnter={() => setChangingTitleId('')}
                                        onBlur={() => setChangingTitleId('')}
                                    />
                                )}
                                {changingTitleId !== fe_id && title}
                            </div>
                            <div className={styles.handler}>
                                <Space>
                                    <Button
                                        size="small"
                                        shape="circle"
                                        className={isHidden ? '' : styles.btn}
                                        icon={<EyeInvisibleOutlined />}
                                        type={isHidden ? 'primary' : 'default'}
                                        onClick={() => handleChangeShowOrHidden(fe_id, !isHidden)}
                                    />
                                    <Button
                                        size="small"
                                        shape="circle"
                                        className={isLocked ? '' : styles.btn}
                                        icon={<LockOutlined />}
                                        type={isLocked ? 'primary' : 'default'}
                                        onClick={() => handleLockedStatus(fe_id)}
                                    />
                                </Space>
                            </div>
                        </div>
                    </SortableItem>
                )
            })}
        </SortableContainer>
    )
}
export default Layers
